package team.nmsg.ge.system.controller;

import java.io.Serializable;
import java.sql.Connection;
import java.util.List;
import java.util.Map;
import java.util.Set;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import javax.sql.DataSource;

import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.IncorrectCredentialsException;
import org.apache.shiro.authc.UsernamePasswordToken;
import org.apache.shiro.session.Session;
import org.apache.shiro.subject.Subject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.CrossOrigin;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.servlet.i18n.SessionLocaleResolver;
import org.springframework.web.servlet.support.RequestContext;

import team.nmsg.ge.system.AppServerConstant;
import team.nmsg.ge.system.bean.AppToken;
import team.nmsg.ge.system.bean.SysBusinessLog;
import team.nmsg.ge.system.bean.SysOper;
import team.nmsg.ge.system.bean.SysRole;
import team.nmsg.ge.system.bean.SysUser;
import team.nmsg.ge.system.exception.NMSTokenCantRefreshException;
import team.nmsg.ge.system.init.SysBusiLogAdditThread;
import team.nmsg.ge.system.service.IAuthenticationService;
import team.nmsg.ge.system.service.IUserRoleService;
import team.nmsg.ge.system.util.ServerConstants;
import team.nmsg.ge.system.util.ServerParams;

import com.alibaba.fastjson.JSONObject;

//@Controller
@CrossOrigin
@RestController
public class CommonController extends BaseController{
	
	private static Logger logger = LoggerFactory.getLogger(CommonController.class);
	
	@Autowired
	private IUserRoleService userRoleService;
	
	@Autowired
	private IAuthenticationService authenticationServiceImpl = null;
	
	@RequestMapping(value = "/login" )
	public JSONObject login(HttpServletRequest req, HttpServletResponse resp) {
		String username = req.getParameter("username");
		String password = req.getParameter("password");
		JSONObject ret = new JSONObject();
		SysUser loginUser = new SysUser();
		loginUser.setUsername(username);
		loginUser.setPassword(password);
		String tokenStr = "";
		try {
			Map<String, Object> retValue = authenticationServiceImpl.userLogin( loginUser );
			
			SysUser userLogin = (SysUser) retValue.get("user");
			AppToken createToken = (AppToken) retValue.get("token");
			
			tokenStr = createToken.createClientToken();
			SysBusinessLog createLoginLog = createLoginLog( username , true);
			SysBusiLogAdditThread.getInstance().addBLog(createLoginLog);
			ret.put(AppServerConstant.KEY_RESULT	, true);
			ret.put("token"	, tokenStr);
			ret.put("user", userLogin.toLoginJson());
			ret.put("auth", createToken.getOpers() );
			ret.put("createTime", createToken.getCreateTime());
			ret.put("expireTime", createToken.getExpireTime());
			ret.put("refreshTime", createToken.getRefreshTime());
		
		} catch (Exception e) {
			ret.put(AppServerConstant.KEY_RESULT	, false);
			SysBusinessLog createLoginLog = createLoginLog( username , false);
			SysBusiLogAdditThread.getInstance().addBLog(createLoginLog);
			if( e instanceof IncorrectCredentialsException ){
				ret.put(AppServerConstant.ERR_KEY_MSG	, e.getMessage());
			}else {
				logger.error( "" ,e );
				ret.put(AppServerConstant.ERR_KEY_MSG	, e.getMessage());
			}
		}
		writeJson(ret, resp);
		return null;
	}
	
	@RequestMapping("/refreshToken")
	public String refreshToken( HttpServletRequest req , HttpServletResponse resp ){
		JSONObject ret = new JSONObject();
		try {
			String tokenStr = getTokenStrFromReq(req);
			
			AppToken fromClientToken = AppToken.fromClientToken(tokenStr);
			Map<String, Object> retValue = authenticationServiceImpl.refreshToken(fromClientToken);
			
			SysUser userLogin = (SysUser) retValue.get("user");
			AppToken createToken = (AppToken) retValue.get("token");
			tokenStr = createToken.createClientToken();
			
			ret.put(AppServerConstant.KEY_RESULT	, true);
			ret.put("token"	, tokenStr);
			ret.put("user", userLogin.toJson());
			ret.put("auth", createToken.getOpers() );
			ret.put("createTime", createToken.getCreateTime());
			ret.put("expireTime", createToken.getExpireTime());
			ret.put("refreshTime", createToken.getRefreshTime());
			
			
		} catch (Exception e) {
			ret.put(AppServerConstant.KEY_RESULT	, false);
			ret.put(AppServerConstant.ERR_KEY_RELOGIN	, true);
			
			if( e instanceof NMSTokenCantRefreshException ){
				//重新登陆
			}else{
				logger.error( "" ,e );
			}
		}
		return ret.toString();
	}
	
	@RequestMapping("/logout")
	public String logout( HttpServletRequest req , HttpServletResponse resp ){
		JSONObject ret = new JSONObject();
		try {
			String tokenStr = getTokenStrFromReq(req);
			
			AppToken fromClientToken = AppToken.fromClientToken(tokenStr);
			boolean userLogout = authenticationServiceImpl.userLogout(fromClientToken);
			
			ret.put(AppServerConstant.KEY_RESULT	, userLogout);
			SysBusinessLog createLogoutLog = createLogoutLog(fromClientToken.getUserName());
			SysBusiLogAdditThread.getInstance().addBLog(createLogoutLog);
		} catch (Exception e) {
			logger.error( "" ,e );
			ret.put(AppServerConstant.KEY_RESULT	, false);
			ret.put(AppServerConstant.ERR_KEY_MSG	, e.getMessage());
		}
		return ret.toString();
	}
	
	@RequestMapping(value = "/helpAndSupport", method = { RequestMethod.POST , RequestMethod.GET } )
	public String helpAndSupport(  HttpServletRequest request  ){
		
		try {
			
		} catch (Exception e) {
			logger.error("", e);
		}
		
		return "/helpAndSupport";
	}
	
	@RequestMapping(value = "/blankPage", method = { RequestMethod.POST , RequestMethod.GET } )
	public String blankPage(  HttpServletRequest request  ){
		
		try {
			
		} catch (Exception e) {
			logger.error("", e);
		}
		
		return "common/blankPage";
	}
	
	
	@RequestMapping(value = "language" , method = { RequestMethod.POST , RequestMethod.GET } )
	public String language( HttpServletRequest  req , HttpServletResponse resp){
		
		try {
			String parameter = req.getParameter("language");
			Subject subject = SecurityUtils.getSubject();
			Session session = subject.getSession();
			if( "zh".equals(parameter)  ){
				session.setAttribute(ServerConstants.SESSION_KEY_LANGUAGE_STR , "zh");
				req.getSession().setAttribute(
						SessionLocaleResolver.LOCALE_SESSION_ATTRIBUTE_NAME, 
						ServerParams.ZH_CN);
			}else if( "en".equals(parameter) ){
				session.setAttribute(ServerConstants.SESSION_KEY_LANGUAGE_STR , "en");
				req.getSession().setAttribute(
						SessionLocaleResolver.LOCALE_SESSION_ATTRIBUTE_NAME, 
						ServerParams.EN_US);
			}
			JSONObject obj = new JSONObject();
			obj.put("result", true);
			writeJson(obj, resp);
		} catch (Exception e) {
			logger.error("" , e);
		}
		
		
		return null;
	}
	
	
	private static SysBusinessLog createLoginLog( String userName, boolean isSuccess ){
		
		SysBusinessLog login = new SysBusinessLog();
		
		login.setOperTimeStamp(System.currentTimeMillis());
		login.setOperKey("1");
		login.setOperDesc("Login");
		login.setOperUserName(userName);
		login.setOperResult(isSuccess+"");
		
		return login;
	}
	
	private static SysBusinessLog createLogoutLog( String userName  ){
		
		SysBusinessLog logout = new SysBusinessLog();
		
		logout.setOperTimeStamp(System.currentTimeMillis());
		logout.setOperKey("1");
		logout.setOperDesc("Logout");
		logout.setOperUserName(userName);
		logout.setOperResult("true");
		
		return logout;
	}
	

	@RequestMapping(value = "/changePassword" , method = { RequestMethod.POST , RequestMethod.GET } )
	public String changePassword(HttpServletRequest req, HttpServletResponse resp) {
		JSONObject obj = new JSONObject();
		try {
			SysUser user=new SysUser();
			String username = req.getParameter("username");
			String oldPassword = req.getParameter("oldPassword");
			String newPassword = req.getParameter("newPassword");
			user.setUsername(username);
			boolean changePassword=userRoleService.updExpiredPassword(user, oldPassword, newPassword);
			obj.put("result", changePassword);
		}catch (Exception e) {	
			logger.error("", e);
		}
		writeJson(obj, resp);
		return null;
	}

	
	
	@RequestMapping(value = "/static/test1" )
	public String test1(HttpServletRequest req, HttpServletResponse resp) {
		JSONObject obj = new JSONObject();
		try {
			obj.put("result", true);
		}catch (Exception e) {	
			logger.error("", e);
		}
		writeJson(obj, resp);
		return null;
	}


}
